PHLEGM v4 - Direct CHR ROM .BIN loading
Checkpoint: 2026-09-27

Added CHR LOAD for loose .BIN files and recursive .ZIP containers, plus CHR STATUS and CHR UNLOAD.

Commodore
- chr_target=firmware-character-rom overlays the configured CHARACTER firmware slot.
- Raw file size must exactly match the machine firmware slot declaration.
- The verified/original slot is retained in memory and restored by CHR UNLOAD.
- Existing bare CHR writable/read-only toggle semantics are preserved.

Nintendo NES
- chr_target=ppu-pattern overlays PPU pattern addresses $0000-$1FFF.
- Raw CHR images are read-only and do not replace/eject cartridge media.
- Mapper 1/MMC1 and mapper 3/CNROM CHR bank state is applied to the overlay.
- Current NES definition accepts 8 KiB through 256 KiB in 8 KiB increments.

Common
- GUI CHR LOAD is an expandable selector backed by /data/chr/; loose .BIN files, .ZIP containers, subdirectories, and nested ZIPs are scanned lazily on expansion.
- The same CHR LOAD selector is exposed under the top-level CHR drop-down; selecting a .bin fills the exact command and double-click executes it.
- The monitor/console form CHR LOAD "file.bin" remains available for explicit paths.
- Direct CHR media survives RESET and POWER cycling.
- State/session format v7 serializes direct CHR media and restores it before VM memory.
- FIRMWARE RELOAD reapplies an active Commodore direct-CHR overlay over the refreshed base firmware.
- MACHINE STATUS reports the direct CHR media state when the selected definition supports it.

Recursive CHR ZIP media:
- /data/chr/ recursively discovers loose .BIN files and .ZIP archives in subdirectories.
- Expanding a ZIP recursively inspects nested ZIP members too; matching .BIN leaves are selectable without extracting the whole archive tree.
- Recursive archive selectors use :: between ZIP layers, e.g. CHR LOAD "fonts.zip" "packs/inner.zip::roms/petscii.bin".
- Only the selected .BIN leaf is materialized to a short-lived temporary file and passed through the same validated CHR loader as a loose .BIN.
- Recursive ZIP nesting is capped at 16 archive layers for bounded resource use.

CHR preview:
- Single-clicking a CHR LOAD .BIN leaf (including recursive ZIP members) previews it without loading; double-click still loads.
- CHR PREVIEW with no path previews the effective active CHR; path/ZIP-member forms preview candidate media.
- Decode format/page size/columns are machine-definition fields (Commodore 1-bpp rows; NES 2-bpp planar tiles).
